import { 
  Inject, 
  Injector, 
  Plugin, 
  CommandType, 
  ICommandService, 
  IUniverInstanceService, 
  UniverInstanceType 
} from '@univerjs/core'
import { DownloadIcon, ExportIcon } from '@univerjs/icons'
import { ComponentManager, IMenuManagerService, MenuItemType, RibbonStartGroup } from '@univerjs/ui'
import type { IAccessor, ICommand } from '@univerjs/core'
import * as XLSX from 'xlsx'

/**
 * Export Plugin
 * 基于Univer官方文档的导出插件
 */
class ExportPlugin extends Plugin {
  static override pluginName = 'export-plugin'

  constructor(
    // inject injector, required
    @Inject(Injector) override readonly _injector: Injector,
    // inject menu service, to add toolbar button
    @Inject(IMenuManagerService) private readonly menuManagerService: IMenuManagerService,
    // inject component manager, to register icon component
    @Inject(ComponentManager) private readonly componentManager: ComponentManager,
    // inject command service, to register command handler
    @Inject(ICommandService) private readonly commandService: ICommandService,
  ) {
    super()
  }

  /** Plugin onStarting lifecycle */
  onStarting() {
    console.log('ExportPlugin onStarting')
    
    // register icon components
    this.componentManager.register('DownloadIcon', DownloadIcon)
    this.componentManager.register('ExportIcon', ExportIcon)

    // CSV导出按钮
    const csvButtonId = 'export-csv-button'
    const csvMenuItemFactory = () => ({
      id: csvButtonId,
      title: 'Export CSV',
      tooltip: 'Export CSV',
      icon: 'DownloadIcon',
      type: MenuItemType.BUTTON,
    })

    this.menuManagerService.mergeMenu({
      [RibbonStartGroup.OTHERS]: {
        [csvButtonId]: {
          order: 20,
          menuItemFactory: csvMenuItemFactory,
        },
      },
    })

    const csvCommand: ICommand = {
      type: CommandType.OPERATION,
      id: csvButtonId,
      handler: (accessor: IAccessor) => {
        console.log('Export CSV button clicked')
        return this.exportToCSV(accessor)
      },
    }

    // Excel导出按钮
    const excelButtonId = 'export-excel-button'
    const excelMenuItemFactory = () => ({
      id: excelButtonId,
      title: 'Export Excel',
      tooltip: 'Export Excel',
      icon: 'ExportIcon',
      type: MenuItemType.BUTTON,
    })

    this.menuManagerService.mergeMenu({
      [RibbonStartGroup.OTHERS]: {
        [excelButtonId]: {
          order: 21,
          menuItemFactory: excelMenuItemFactory,
        },
      },
    })

    const excelCommand: ICommand = {
      type: CommandType.OPERATION,
      id: excelButtonId,
      handler: (accessor: IAccessor) => {
        console.log('Export Excel button clicked')
        return this.exportToExcel(accessor)
      },
    }

    // register command handlers
    this.commandService.registerCommand(csvCommand)
    this.commandService.registerCommand(excelCommand)
  }

  /**
   * 导出为CSV
   */
  private async exportToCSV(accessor: IAccessor): Promise<boolean> {
    try {
      const univerInstanceService = accessor.get(IUniverInstanceService)
      
      // get current workbook
      const workbook = univerInstanceService.getCurrentUnitOfType(UniverInstanceType.UNIVER_SHEET)
      if (!workbook) {
        throw new Error('No active workbook found')
      }

      // get active sheet
      const worksheet = (() => {
        try {
          const wb = workbook as any
          if (typeof wb.getActiveSheet === 'function') {
            return wb.getActiveSheet()
          } else if (typeof wb.getSheets === 'function') {
            const sheets = wb.getSheets()
            return sheets?.[0]
          }
          return null
        } catch (error) {
          console.warn('Failed to get active sheet:', error)
          return null
        }
      })()
      if (!worksheet) {
        throw new Error('No active worksheet found')
      }

      // 安全地获取单元格数据
      let cellData: any = {}
      
      try {
        // 尝试获取单元格数据
        if (typeof worksheet.getCellData === 'function') {
          cellData = worksheet.getCellData()
        } else if (typeof worksheet.getRange === 'function') {
          // 使用 getRange 方法获取数据
          const maxRow = 1000 // 假设最大行数
          const maxCol = 100  // 假设最大列数
          const range = worksheet.getRange(0, 0, maxRow, maxCol)
          if (range && typeof range.getValues === 'function') {
            const values = range.getValues()
            // 将二维数组转换为 cellData 格式
            values.forEach((row: any[], rowIndex: number) => {
              cellData[rowIndex] = {}
              row.forEach((value: any, colIndex: number) => {
                if (value !== null && value !== undefined && value !== '') {
                  cellData[rowIndex][colIndex] = { v: value }
                }
              })
            })
          }
        } else {
          console.warn('无法获取单元格数据，使用空数据')
          cellData = {}
        }
      } catch (error) {
        console.warn('获取单元格数据失败:', error)
        cellData = {}
      }

      if (!cellData || typeof cellData !== 'object' || Object.keys(cellData).length === 0) {
        alert('表格中没有数据可导出')
        return false
      }

      // 转换为CSV格式
      const csvContent = this.cellsToCSV(cellData)
      
      // 下载文件
      this.downloadFile(csvContent, 'univer-sheet.csv', 'text/csv')
      
      console.log('CSV文件导出成功')
      return true
    } catch (error) {
      console.error('CSV导出失败:', error)
      alert('CSV导出失败: ' + (error instanceof Error ? error.message : String(error)))
      return false
    }
  }

  /**
   * 导出为Excel
   */
  private async exportToExcel(accessor: IAccessor): Promise<boolean> {
    try {
      const univerInstanceService = accessor.get(IUniverInstanceService)
      
      // get current workbook
      const workbook = univerInstanceService.getCurrentUnitOfType(UniverInstanceType.UNIVER_SHEET)
      if (!workbook) {
        throw new Error('No active workbook found')
      }

      // get active sheet
      const worksheet = (() => {
        try {
          const wb = workbook as any
          if (typeof wb.getActiveSheet === 'function') {
            return wb.getActiveSheet()
          } else if (typeof wb.getSheets === 'function') {
            const sheets = wb.getSheets()
            return sheets?.[0]
          }
          return null
        } catch (error) {
          console.warn('Failed to get active sheet:', error)
          return null
        }
      })()
      if (!worksheet) {
        throw new Error('No active worksheet found')
      }

      // 安全地获取单元格数据
      let cellData: any = {}
      
      try {
        // 尝试获取单元格数据
        if (typeof worksheet.getCellData === 'function') {
          cellData = worksheet.getCellData()
        } else if (typeof worksheet.getRange === 'function') {
          // 使用 getRange 方法获取数据
          const maxRow = 1000 // 假设最大行数
          const maxCol = 100  // 假设最大列数
          const range = worksheet.getRange(0, 0, maxRow, maxCol)
          if (range && typeof range.getValues === 'function') {
            const values = range.getValues()
            // 将二维数组转换为 cellData 格式
            values.forEach((row: any[], rowIndex: number) => {
              cellData[rowIndex] = {}
              row.forEach((value: any, colIndex: number) => {
                if (value !== null && value !== undefined && value !== '') {
                  cellData[rowIndex][colIndex] = { v: value }
                }
              })
            })
          }
        } else {
          console.warn('无法获取单元格数据，使用空数据')
          cellData = {}
        }
      } catch (error) {
        console.warn('获取单元格数据失败:', error)
        cellData = {}
      }

      if (!cellData || typeof cellData !== 'object') {
        alert('表格中没有数据可导出')
        return false
      }

      // 转换为二维数组
      const worksheetData = this.cellsToArray(cellData)
      
      // 创建新的工作簿
      const excelWorkbook = XLSX.utils.book_new()
      
      // 创建工作表
      const ws = XLSX.utils.aoa_to_sheet(worksheetData)
      
      // 添加工作表到工作簿
      XLSX.utils.book_append_sheet(excelWorkbook, ws, 'Sheet1')
      
      // 生成Excel文件
      const excelBuffer = XLSX.write(excelWorkbook, { bookType: 'xlsx', type: 'array' })
      
      // 下载文件
      const blob = new Blob([excelBuffer], { 
        type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet' 
      })
      const url = URL.createObjectURL(blob)
      const link = document.createElement('a')
      link.href = url
      link.download = 'univer-sheet.xlsx'
      document.body.appendChild(link)
      link.click()
      document.body.removeChild(link)
      URL.revokeObjectURL(url)
      
      console.log('Excel文件导出成功')
      return true
    } catch (error) {
      console.error('Excel导出失败:', error)
      alert('Excel导出失败: ' + (error instanceof Error ? error.message : String(error)))
      return false
    }
  }

  /**
   * 替代方法获取单元格数据
   */
  private getCellDataAlternative(worksheet: any): any {
    try {
      // 尝试使用其他可能的方法获取数据
      if (typeof worksheet.getRange === 'function') {
        // 尝试获取一个较大的范围
        const maxRow = 1000
        const maxCol = 100
        const range = worksheet.getRange(0, 0, maxRow, maxCol)
        if (range && typeof range.getValues === 'function') {
          const values = range.getValues()
          // 将二维数组转换为 cellData 格式
          const cellData: any = {}
          values.forEach((row: any[], rowIndex: number) => {
            cellData[rowIndex] = {}
            row.forEach((value: any, colIndex: number) => {
              if (value !== null && value !== undefined && value !== '') {
                cellData[rowIndex][colIndex] = { v: value }
              }
            })
          })
          return cellData
        }
      }
      
      // 如果其他方法都失败，返回空数据
      console.warn('无法获取单元格数据，返回空数据')
      return {}
    } catch (error) {
      console.error('获取单元格数据失败:', error)
      return {}
    }
  }

  /**
   * 将单元格数据转换为CSV格式
   */
  private cellsToCSV(cellData: any): string {
    const cells: { row: number; column: number; value: string }[] = []
    
    // 遍历所有单元格数据
    Object.keys(cellData).forEach(rowKey => {
      const rowData = cellData[rowKey]
      if (rowData && typeof rowData === 'object') {
        Object.keys(rowData).forEach(colKey => {
          const cell = rowData[colKey]
          if (cell && (cell.v !== undefined || cell.f !== undefined)) {
            cells.push({
              row: parseInt(rowKey),
              column: parseInt(colKey),
              value: cell.v || ''
            })
          }
        })
      }
    })

    if (cells.length === 0) return ''

    // 找到最大行和列
    const maxRow = Math.max(...cells.map(cell => cell.row))
    const maxCol = Math.max(...cells.map(cell => cell.column))

    // 创建二维数组
    const grid: string[][] = []
    for (let row = 0; row <= maxRow; row++) {
      grid[row] = []
      for (let col = 0; col <= maxCol; col++) {
        grid[row][col] = ''
      }
    }

    // 填充数据
    cells.forEach(cell => {
      grid[cell.row][cell.column] = cell.value || ''
    })

    // 转换为CSV格式
    return grid.map(row => 
      row.map(cell => `"${cell.replace(/"/g, '""')}"`).join(',')
    ).join('\n')
  }

  /**
   * 将单元格数据转换为二维数组
   */
  private cellsToArray(cellData: any): any[][] {
    const cells: { row: number; column: number; value: any }[] = []
    
    // 遍历所有单元格数据
    Object.keys(cellData).forEach(rowKey => {
      const rowData = cellData[rowKey]
      if (rowData && typeof rowData === 'object') {
        Object.keys(rowData).forEach(colKey => {
          const cell = rowData[colKey]
          if (cell && (cell.v !== undefined || cell.f !== undefined)) {
            cells.push({
              row: parseInt(rowKey),
              column: parseInt(colKey),
              value: cell.v || ''
            })
          }
        })
      }
    })

    if (cells.length === 0) return [[]]

    // 找到最大行和列
    const maxRow = Math.max(...cells.map(cell => cell.row))
    const maxCol = Math.max(...cells.map(cell => cell.column))

    // 创建二维数组
    const grid: any[][] = []
    for (let row = 0; row <= maxRow; row++) {
      grid[row] = []
      for (let col = 0; col <= maxCol; col++) {
        grid[row][col] = ''
      }
    }

    // 填充数据
    cells.forEach(cell => {
      grid[cell.row][cell.column] = cell.value || ''
    })

    return grid
  }

  /**
   * 下载文件
   */
  private downloadFile(content: string, filename: string, mimeType: string) {
    const blob = new Blob([content], { type: mimeType })
    const url = URL.createObjectURL(blob)
    const link = document.createElement('a')
    link.href = url
    link.download = filename
    document.body.appendChild(link)
    link.click()
    document.body.removeChild(link)
    URL.revokeObjectURL(url)
  }
}

export default ExportPlugin
